package awesome.cpu.structure;

import awesome.cpu.utils.Mode;

public class Mux2PC extends NonSequentialComponent {
	
	public final static int KEY_PC_SRC = 1;
	private int mPCSrc;
	
	private static boolean outputDebug = false;
	
	public final static int KEY_PC_NEXT = 2;
	private int mPCNext;
	public final static int KEY_PC_BRANCH = 3;
	private int mPCBranch;
	public final static int KEY_PC_JUMP = 4;
	private int mPCJump;
	
	public final static int KEY_SELECTED = 5;
	//private int mSelected;
	
	private final static Mux2PC mInstance = new Mux2PC();
	
	private Mux2PC() {}
	
	public static Mux2PC getInstance() {
		return mInstance;
	}

	@Override
	boolean setData(int keyInterface, int data) {
		switch (keyInterface) {
		case KEY_PC_SRC:
			mPCSrc = data;
			return true;
		case KEY_PC_NEXT:
			mPCNext = data;
			return true;
		case KEY_PC_BRANCH:
			mPCBranch = data;
			return true;
		case KEY_PC_JUMP:
			mPCJump = data;
			return true;
		}
		return false;
	}

	@Override
	int getData(int keyInterface) {
		BusMonitor.transferData(Control.getInstance(), Control.KEY_PC_SOURCE,
				this, KEY_PC_SRC);
		BusMonitor.transferData(ALU.getInstance(), ALU.KEY_ALU_RESULT_31_0,
				this, KEY_PC_NEXT);
		BusMonitor.transferData(ALUOut.getInstance(), ALUOut.KEY_ALU_OUT_LO,
				this, KEY_PC_BRANCH);
		BusMonitor.transferData(RegBShifter.getInstance(), RegBShifter.KEY_RESULT,
				this, KEY_PC_JUMP);
		
		switch (keyInterface) {
		case KEY_SELECTED:
			int s = select();
			if (outputDebug && Mode.getDebugLevel() >= Mode.DEBUG_LEVEL_PRINT_ALL)
				System.out.println("Mux2PC selected = " + s);
			return s;
		}
		return 0;
	}

	private int select() {
		switch (mPCSrc) {
		case 0:
			return mPCNext;
		case 1:
			return mPCBranch;
		case 2:
			return mPCJump;
		}
		return 0;
	}
}
